#include "./../../../include/online/CacheSystem/TimerManager.h"
#include "./../../../include/online/Tools/MyLogger.h"
#include "./../../../include/online/CacheSystem/MyTask.h"
#include <stdlib.h>
#include <sys/timerfd.h>
#include <sys/epoll.h>
#include <unistd.h>
#include <algorithm>
#include <mutex>

// 静态成员变量初始化
TimerManager *TimerManager::_pInstance = nullptr;
pthread_once_t TimerManager::_once = PTHREAD_ONCE_INIT;

// 获取 TimerManager 单例
TimerManager *TimerManager::getTimerManager()
{
    pthread_once(&_once, init_r);
    return _pInstance;
}

// 初始化定时器
void TimerManager::initTimer(int initSec, int periodSec)
{
    _initSec = initSec;
    _periodSec = periodSec;
}

// 启动定时器并监听事件
void TimerManager::start()
{
    int epfd = epoll_create1(0);
    if (epfd == -1)
    {
        LogError("epoll_create1 failed");
        return;
    }
    if (_timerfd == -1)
    {
        LogError("Invalid timerfd, cannot add to epoll");
        close(epfd);
        return;
    }

    MyTask task;
    _pInstance->attach(&task);
    
    // 设置定时器
    setTimerfd(_initSec, _periodSec);

    // 监听 timerfd 事件
    struct epoll_event timer_event;
    timer_event.events = EPOLLIN;
    timer_event.data.fd = _timerfd;

    // 将定时器文件描述符加入 epoll 监听
    int ret = epoll_ctl(epfd, EPOLL_CTL_ADD, _timerfd, &timer_event);
    if (ret == -1)
    {
        LogError("epoll_ctl failed");
        close(epfd);
        return;
    }

    _isStarted = true;
    struct epoll_event events[2];
    while (_isStarted)
    {
        int nready = epoll_wait(epfd, events, 2, 5000); // 等待epoll事件，最多阻塞5秒
        if (nready == -1 && errno == EINTR)             // 如果被中断，继续等待
        {
            continue;
        }
        else if (nready == -1)
        {
            LogError("nready == -1,定时器出问题了!"); // 输出错误信息
            return;
        }
        else if (nready == 0)
        {
            continue;
        }
        for (int i = 0; i < nready; ++i)
        {
            if (events[i].data.fd == _timerfd)
            {
                handleRead();      // 处理定时器触发事件
                processTasks();    // 执行定时任务
            }
        }
    }
    return;
}

// 停止定时器
void TimerManager::stop()
{
    _isStarted = false;
    if (_timerfd != -1)
    {
        setTimerfd(0, 0); // 关闭定时器
        close(_timerfd);
        _timerfd = -1;
    }
}

// 添加任务
void TimerManager::attach(TimerTask *task)
{
    std::lock_guard<std::mutex> lock(_mutex);
    if (std::find(_wheelList.begin(), _wheelList.end(), task) == _wheelList.end())
    {
        _wheelList.push_back(task);
    }
}

// 移除任务
void TimerManager::detach(TimerTask *task)
{
    std::lock_guard<std::mutex> lock(_mutex);
    auto it = std::find(_wheelList.begin(), _wheelList.end(), task);
    if (it != _wheelList.end())
    {
        _wheelList.erase(it);
    }
}

// 创建 timerfd
int TimerManager::createTimerfd()
{
    int fd = timerfd_create(CLOCK_REALTIME, 0);
    if (fd == -1)
    {
        LogError("Failed to create timerfd");
    }
    return fd;
}

// 设置定时器触发时间
void TimerManager::setTimerfd(int initSec, int periodSec)
{
    if (_timerfd == -1)
    {
        LogError("Invalid timerfd in setTimerfd");
        return;
    }

    struct itimerspec newValue;

    // 设置初始时间
    newValue.it_value.tv_sec = initSec;
    newValue.it_value.tv_nsec = 0;

    // 设置周期时间
    newValue.it_interval.tv_sec = periodSec;
    newValue.it_interval.tv_nsec = 0;

    int ret = timerfd_settime(_timerfd, 0, &newValue, nullptr);
    if (ret == -1)
    {
        LogError("Failed to set timerfd");
    }
}

// 读取定时器触发事件
void TimerManager::handleRead()
{
    uint64_t exp;
    ssize_t ret = read(_timerfd, &exp, sizeof(uint64_t));

    if (ret == -1)
    {
        if (errno == EINTR)
        {
            LogError("Read interrupted, retrying...");
            return;
        }
        LogError("Read error");
    }
    else if (ret != sizeof(uint64_t))
    {
        LogError("Incomplete read from timerfd");
    }
}

// 执行所有定时任务
void TimerManager::processTasks()
{
    std::vector<TimerTask *> tasks;
    {
        std::lock_guard<std::mutex> lock(_mutex);
        tasks = _wheelList; // 复制任务列表，避免死锁
    }
    for (auto &task : tasks)
    {
        task->process(); // 执行任务
    }
}

// 构造函数
TimerManager::TimerManager()
    : _timerfd(createTimerfd()), _isStarted(false)
{
    if (_timerfd != -1)
    {
        initTimer(1, 6); // 初始化定时器
    }
}

// 析构函数
TimerManager::~TimerManager()
{
}

// 初始化单例
void TimerManager::init_r()
{
    if (_pInstance == nullptr)
    {
        _pInstance = new TimerManager();
        atexit(destroy);
    }
}

// 释放单例
void TimerManager::destroy()
{
    if (_pInstance)
    {
        delete _pInstance;
        _pInstance = nullptr;
    }
}
